package com.powerunion.datacollection.report.excelreport.base.element;

import java.text.DateFormat;
import java.text.ParseException;
import java.util.Date;

import com.powerunion.datacollection.report.excelreport.Logger;
import com.powerunion.datacollection.report.excelreport.base.Parameter;


/**
 * TODO: 字段变量类：
 *		任何需要取值得地方都可以动态构建相应的变量对象来实现，如想从数据源中取得
 *		某个字段的值，我们可以构建一个字段类变量的实例，通过该实例就可以取得该数据源的值。
 *		
 *		一个字段变量类是对生成器中具体使用到的变量的一种抽象，
 *		变量是一个可以动态取得其值的对象，当然这个值可能是从某个数据源去取，
 *		或者是从某个参数中去取等，要看具体子类的实现。
 * @author juny
 */
public abstract class Variable {
    private static Logger log = Logger.getLogger(Variable.class);
    /**
     * 取得变量的值,
     * @return
     * @throws Exception
     */
    public abstract Object getValue() throws Exception ;
    
    /**
     * 给当前变量事例设置参数,因为任何变量都是跟特定的参数所关联的,
     * 比如字段型变量要与某个数据源所关联,而参数型变量又跟某个参数所关联.
     * 本函数用来初始化各变量的关联对象.
     * @param param
     */
    public void setParam(Parameter param){
        ;
    }
    
    /**
     * 取得当前变量名称
     * @return
     */
    public String getName(){
        return name;
    }
    
    /**
     * 设置当前变量名称
     * @param name
     */
    protected void setName(String name){
        this.name = name;
    }
    
    /**
     * 以字符串形式返回变量的值，忽略变量的具体类型
     */
    public abstract String getString()throws Exception;
    
    /**
     * 取得当前变量对象的类型
     */
    public byte getType(){
        return 0;//Unknown
    }
    
    /**
     * 设置数据变量的类型
     */
    public void setValueType(String type){
        this.type = type;
    }
    
    /**
     * 根据变量定义的类型，将参数值转换成变量指定类型的值
     * 	如果传入变量是配置的类型则直接返回.
     * 	如果传入的变量类型未定义则直接返回传入参数
     * @param value
     * @return
     */
    protected Object getValueByType(Object value){
        try{
            if(this.type.equals(UNKNOWN)){
                return value;
            }
            
            if(this.type.equals(STRING)){
                return value.toString();
            }
            
            if(this.type.equals(INTEGER)){
                if(value instanceof Integer){
                    return value;
                }
                return new Integer(value.toString());
            }
            
            if(this.type.equals(LONG)){
                if(value instanceof Long){
                    return value;
                }
                return new Long(value.toString());
            }
            
            if(this.type.equals(FLOAT)){
                if(value instanceof Float){
                    return value;
                }
                return new Float(value.toString());
            }
            
            if(this.type.equals(DOUBLE)){
                if(value instanceof Double){
                    return value;
                }
                return new Double(value.toString());
            }
            
            if(this.type.equals(DATE)){
                if(value instanceof Date){
                    return value;
                }
                return DateFormat.getDateInstance().parse(value.toString());
            }
            
            if(this.type.equals(SHORT)){
                if(value instanceof Short){
                    return value;
                }
                return new Short(value.toString());
            }
            
            if(this.type.equals(BOOLEAN)){
                if(value instanceof Boolean){
                    return value;
                }
                return new Boolean(value.toString());
            }
            
            if(this.type.equals(BYTE)){
                if(value instanceof Byte){
                    return value;
                }
                return new Byte(value.toString());
            }
        }catch(NumberFormatException e){
            log.error("Couldn't convert " + value +
                     " into type(" + type + "). Error message: " + e.getMessage()
                    );
        } catch (ParseException e) {
            log.error("Couldn't convert " + value +
                    " into type(" + type + "). Error message: " + e.getMessage()
                   , e);
        }
        //不能转换则返回传入值
        return value;
    }
    private String type = null;
    private String name = null;
    public final static byte VARIABLE_TYPE_PARAMETER = 1; //标识为参赛类型
    public final static byte VARIABLE_TYPE_FIELD = 2;//标识当前对象为字段变量类型
    public final static byte VARIABLE_TYPE_CONSTANT = 3;//标识当前对象为常量
    //定义数据源支持的类型
    public final static String INTEGER = "java.lang.Integer";
    public final static String BYTE = "java.lang.Byte";
    public final static String DOUBLE = "java.lang.Double";
    public final static String FLOAT = "java.lang.Float";
    public final static String LONG = "java.lang.Long";
    public final static String SHORT = "java.lang.Short";
    public final static String STRING = "java.lang.String";
    public final static String BOOLEAN = "java.lang.Boolean";
    public final static String DATE = "java.util.Date";
    
    public final static String UNKNOWN = "";
}
